/**
 * Author(s): xuming.Wong <xuming.Wong@gmail.com>
 */
#include "GameWorld.h"
#include "InputSystem.h"
#include "Application.h"

namespace OgreCamNav
{
	GameWorld::GameWorld(void)
	{
		rightMouseDown=false;
		character=NULL;
	}

	GameWorld::~GameWorld(void)
	{
	}

	GameWorld &GameWorld::getSingleton()
	{
		static GameWorld world;
		return world;
	}

	void GameWorld::init(Ogre::RenderWindow* win)
	{
		_root=Ogre::Root::getSingletonPtr();
		_win=win;
		sceneMgr = _root->createSceneManager(Ogre::ST_EXTERIOR_CLOSE);
		camera=sceneMgr->createCamera("MainCamera");

		setupScene();
		setupGUI();
		setupViewport();
		setupInputListener();

		createMainCharacter();
	}

	void GameWorld::createMainCharacter()
	{
		character=new SinbadCharacter(camera);
		character->setPostion(700,0,700);
	}

	void GameWorld::setupGUI()
	{
		//GUISystem::getSingleton().setupGUI(TEST_WORLD_2_GUI,_win,sceneMgr);	
	}

	void GameWorld::setupInputListener()
	{
		InputSystem::getSingleton().addKeyListener(this,"TestWorld2KeyListener");
		InputSystem::getSingleton().addMouseListener(this,"TestWorld2MouseListener");
	}

	void GameWorld::setupScene()
	{
		//Set ambient light
		sceneMgr->setAmbientLight(Ogre::ColourValue(1,1, 1));
		sceneMgr->setSkyDome(true, "Examples/CloudySky", 5, 8);

		// World geometry
		sceneMgr->setWorldGeometry("terrain.cfg");		
		//raySceneQuery = sceneMgr->createRayQuery(Ogre::Ray());
		
	}

	void GameWorld::setupViewport()
    {
        // Create one viewport, entire window
		Ogre::Viewport* vp = _win->addViewport(camera);
		vp->setBackgroundColour(Ogre::ColourValue(0,0,0));

        // Alter the camera aspect ratio to match the viewport
        camera->setAspectRatio(Ogre::Real(vp->getActualWidth()) / Ogre::Real(vp->getActualHeight()));
    }

	void GameWorld::update(float deltaT)
	{
		if(character!=NULL){
			character->update(deltaT);
		}
	}

	bool GameWorld::keyPressed(const OIS::KeyEvent &e)
	{
		switch(e.key){
			case OIS::KC_ESCAPE:
				Application::getSingleton().shutdown();
				return false;

		}
		/*
		CEGUI::System *sys = CEGUI::System::getSingletonPtr();
		sys->injectKeyDown(e.key);
		sys->injectChar(e.text);
		*/

		character->injectKeyDown(e);
		return true;
	}

	bool GameWorld::keyReleased( const OIS::KeyEvent &e)
	{
		/*
		if(CEGUI::System::getSingleton().injectKeyUp(e.key)){
			return true;
		}
		*/

		character->injectKeyUp(e);
		return true;
	}

	bool GameWorld::mouseMoved( const OIS::MouseEvent &e)
	{
		/*
		if(CEGUI::System::getSingleton().injectMouseMove(e.state.X.rel, e.state.Y.rel)){
			return true;
		}
		*/
		character->injectMouseMove(e);
		return true;
	}

	bool GameWorld::mousePressed( const OIS::MouseEvent &e, OIS::MouseButtonID id)
	{
		/*
		if(CEGUI::System::getSingleton().injectMouseButtonDown(Utility::convertButton(id))){
			return true;
		}
		*/
		character->injectMouseDown(e,id);
		return true;
	}
	
	bool GameWorld::mouseReleased( const OIS::MouseEvent &e, OIS::MouseButtonID id )
	{
		/*
		if(CEGUI::System::getSingleton().injectMouseButtonUp(Utility::convertButton(id))){
			return true;
		}
		*/
		rightMouseDown=false;
		return true;
	}
}
